package edu.berkeley.cs160.innovationers.shoppersidekick;

import java.io.IOException;
import java.util.ArrayList;
import java.util.ListIterator;

import java.util.List;

import org.json.JSONException;
import org.json.JSONObject;

import edu.berkeley.cs160.innovationers.shoppersidekick.ItemView.BackgroundThread;
import edu.berkeley.cs160.innovationers.shoppersidekick.database.MyDB;
import edu.berkeley.cs160.innovationers.shoppersidekick.rpclib.Configuration;
import edu.berkeley.cs160.innovationers.shoppersidekick.rpclib.ShopperSidekickProtocol;
import edu.berkeley.cs160.innovationers.shoppersidekick.sync.JSONRPCMethod;
import edu.berkeley.cs160.innovationers.shoppersidekick.sync.RPCClient;
import edu.berkeley.cs160.innovationers.shoppersidekick.test.TestRPCActivity;


import android.app.Activity;
import android.app.AlertDialog;
import android.app.Application;
import android.app.ListActivity;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.database.Cursor;
import android.database.sqlite.SQLiteException;
import android.graphics.Color;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.view.ContextMenu;
import android.view.ContextMenu.ContextMenuInfo;
import android.view.KeyEvent;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnLongClickListener;
import android.view.ViewGroup;
import android.view.View.OnClickListener;
import android.widget.AdapterView.AdapterContextMenuInfo;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.ListView;
import android.widget.TextView;
import android.widget.Toast;

public class ShopperSidekick extends ListActivity {
    private MyListAdapter adapter;
    private ArrayList<ShoppingList> myList;
    private ArrayList<Member> myMember;
    private ListActivity myself;
    private myApp appInfo;
    private boolean isNew = true;
    private boolean isNewMem = true;
    private MyDB localDatabase;
    
BackgroundThread backgroundThread;
    
    public class BackgroundThread extends Thread {

    	 boolean running = false;

    	 void setRunning(boolean b){
    	  running = b;
    	 }

    	 @Override
    	 public void run() {
    	  // TODO Auto-generated method stub
    	  //super.run();
    	  while(running){
    	   try {
    	    sleep(8000);
				Log.d(Config.SS_TAG, "Add List Item button called.");
				JSONRPCMethod createList;
				try {
					createList = new JSONRPCMethod.Sync(appInfo.getC2DMUser());
					//createList = new JSONRPCMethod.Sync("nadirabid@gmail.com");
					JSONObject returnValue = RPCClient.execute(createList); 
					RPCClient.resolveSyncData(returnValue, appInfo);
					
					Log.e(Config.SS_TAG, returnValue.getString("success"));
					Log.d(Config.SS_TAG, returnValue.toString());
					
				} catch (JSONException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			
    	   } catch (InterruptedException e) {
    	    // TODO Auto-generated catch block
    	    e.printStackTrace();
    	   }
    	   handler.sendMessage(handler.obtainMessage());
    	  }
    	 }

    	}

    
    //do the background sync
    
    
    Handler handler = new Handler(){

    	
    	//DO SYNC HERE
    	 @Override
    	 public void handleMessage(Message msg) {
    	  // TODO Auto-generated method stub
    	  //super.handleMessage(msg);
    		 //CompareData compareData=new CompareData()
    		 	//myList.clear();
    		 	//myList.addAll(appInfo.getShoppingList());
    		 	//localDatabase.insertListData(myShoppingList);
				adapter.notifyDataSetChanged();
    	 }

    	};
    	
    public void RPCAddList(String ListTitle) {
    	
    	
		Log.d(Config.SS_TAG, "Create list button called.");

		try {
			JSONRPCMethod createList = new JSONRPCMethod.CreateList(ListTitle, appInfo.getC2DMUser());
			
			JSONObject returnValue = RPCClient.execute(createList);
			
			String ret = returnValue.getString(ShopperSidekickProtocol.CreateList.RETURN[0]);
			
			Log.d(Config.SS_TAG, "Message Received: " + ret);
		} catch (JSONException e) {
			Log.e(Config.SS_TAG,"We got an error while making the object");
			e.printStackTrace();
		}
		
		
	}
    
	
    @Override
	public void onActivityResult(int requestCode,int resultCode,final Intent data) {
		super.onActivityResult(requestCode, resultCode, data);
		switch(requestCode) {
		
			case myApp.login:
				UpdateTitle();
				break;
			case myApp.addList: //list added
				if (resultCode == myApp.newList){
					final ShoppingList temp = new ShoppingList(data.getCharSequenceExtra("CONTENT").toString());
					temp.setOwner(appInfo.getUserName());
					myList.add(0,temp);
					Log.v("test1", "10");
					localDatabase.insertdiary("first", "X", data.getCharSequenceExtra("CONTENT").toString());
					Log.v("test1", "11");
					adapter.notifyDataSetChanged();
					
					//make rpc call to add list to server in background
				    Thread background = new Thread (new Runnable() {
				    	public void run() {
				    		RPCAddList(temp.getName());
				    	}
				        
				    }    
				    );
				    background.start();
	        		updateApp();
				}
				break;
			case myApp.listView:
				if (resultCode == myApp.listChanged){
					localDatabase.open();
					myList = appInfo.getShoppingList();
					adapter.notifyDataSetChanged();
					updateApp();
				}
				break;
			case myApp.editMember:
				if (resultCode == myApp.memberChanged){
					myMember = appInfo.getMemberList();

					
					updateApp();
				}
				break;
			case myApp.renameList:
				if (resultCode == myApp.listNameChanged){
					myList = appInfo.getShoppingList();
					
					
					
					adapter.notifyDataSetChanged();
					updateApp();
				}
		}
		hint();
	}
    
    private void UpdateTitle() {
    	TextView title = (TextView) findViewById(R.id.Title);
    	title.setText(appInfo.getUserName()+"'s Shopping Lists");
    }
    
    @Override
    public void onCreate(Bundle savedInstanceState) {
    	
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        setTitle("Shopper's Sidekick");
    	appInfo = (myApp) getApplication();
    	if(!appInfo.isLogin()){
    		Intent intent = new Intent(ShopperSidekick.this, Login.class);
    		startActivityForResult(intent, myApp.login);  
    	}
    	Log.v("test1", "open");
    	
        //start the database
        localDatabase = new MyDB(this);
        localDatabase.open();
        
    	TextView title = (TextView) findViewById(R.id.Title);
    	title.setText(appInfo.getUserName()+"'s Shopping Lists");

        
        
       
        getdata(appInfo.getUserName());
        getMembers(appInfo.getUserName());
        
        if(isNew){
        myself = this;
        appInfo.setCurrentActivity(this);
        myList = new ArrayList<ShoppingList>();
        appInfo.setShoppingList(myList);
        }else{
        	myself = this;
        	appInfo.setCurrentActivity(this);
        	appInfo.setShoppingList(myList);
        }
        
        if(isNewMem){
            myMember = new ArrayList<Member>();
            appInfo.setMemberList(myMember);
            }else{
            	appInfo.setMemberList(myMember);
            }
        
        final Button AddButton=(Button)findViewById(R.id.AddButton);
        AddButton.setOnClickListener(new OnClickListener(){
        	public void onClick(View view){
        		Intent myIntent = new Intent(ShopperSidekick.this, AddList.class);
        		startActivityForResult(myIntent,myApp.addList);   
        	}
        }
        );
        
        final Button OptionButton = (Button)findViewById(R.id.Option);
        OptionButton.setOnClickListener(new OnClickListener(){
        	public void onClick(View view){
        		Log.v("option","1");
        		myself.openOptionsMenu();
        		Log.v("option","2");
        	}
        });
        
        final Button BackButton = (Button)findViewById(R.id.closeApp);
        BackButton.setOnClickListener(new OnClickListener(){
        	public void onClick(View view){
        		localDatabase.deleteALLData();
        		localDatabase.insertALLData(appInfo.getShoppingList());
        		localDatabase.close();
        		myself.finish();
        	}
        });        

        
        adapter=new MyClickableShoppingListListAdapter(myList,this);
        getListView().setAdapter(adapter);
        
        hint();
        
        backgroundThread = new BackgroundThread();
        backgroundThread.setRunning(true);
        backgroundThread.start();
    }
    public void getMembers(String string){
    	
    	ArrayList<String> subList;
    	subList = new ArrayList<String> ();
    	
    	Log.v("test0", "0");
    	try{
        Cursor c = localDatabase.getMembers();
        isNewMem = false;
    	
        Log.v("test1", "1");
        
        startManagingCursor(c);
        
        	Log.v("test3", "3");
        	if(c.getCount()!=0){
        	if(c.moveToFirst()){
        		Log.v("test4","4");
        		 myMember = new ArrayList<Member>();
        		do{
        			Log.v("test5","5");
        			String itemName, quantity, listName;
        			itemName = c.getString(c.getColumnIndex(Constants.ITEM_NAME));
        			quantity = c.getString(c.getColumnIndex(Constants.QUANTITY_NAME));
        			listName = c.getString(c.getColumnIndex(Constants.LIST_NAME));
        			
        			if(listName.equals("M")){
        				Member newMem = new Member();
        				newMem.setName(itemName);
        				myMember.add(newMem);
        				//set pic in future
        			}
        			
        			
        			
        		}while(c.moveToNext());
        	}}else{
        		isNewMem = true;
        	}
        		}catch(SQLiteException ex){
        			isNewMem = true;
        			return;
        		}
    	
    }
    
    public void getdata(String userName){
    	
    	ArrayList<String> subList;
    	subList = new ArrayList<String> ();
    	
    	Log.v("test0", "0");
    	try{
        Cursor c = localDatabase.getdiaries();
        isNew = false;
    	
        Log.v("test1", "1");
        
        startManagingCursor(c);
        
        	Log.v("test3", "3");
        	if(c.getCount()!=0){
        	if(c.moveToFirst()){
        		Log.v("test4","4");
        		do{
        			Log.v("test5","5");
        			String itemName, quantity, listName;
        			itemName = c.getString(c.getColumnIndex(Constants.ITEM_NAME));
        			quantity = c.getString(c.getColumnIndex(Constants.QUANTITY_NAME));
        			listName = c.getString(c.getColumnIndex(Constants.LIST_NAME));
        			
        			if(!listName.equals("M")){
        			Log.v("test6","6");
        			boolean checkList = false;
        			ListIterator<String> ptr;
        			Log.v("test6","6.5");
        			
        			if(myList != null){
        			ptr = subList.listIterator();
        			Log.v("test7","7");
        			while(ptr.hasNext()){
        				if(ptr.next().equals(listName))
        					{
                			Log.v("test8","true");

        					checkList = true;
        					break;
        					}
        			}}else{
        				myList = new ArrayList<ShoppingList>();
        			}
        			Log.v("test8","8");
        			if(checkList){
            			/*
        				Log.v("test8","T");
            			ShoppingList newList = new ShoppingList(listName);
        				int index = myList.indexOf(newList);
        				if(!itemName.equals("first")){
            			myList.get(index).addItem(itemName, quantity);
        				}*/
        				
        			}else{
            			
            			ShoppingList newList = new ShoppingList(listName);
            			
            			
            			Cursor cList = localDatabase.getspecificlist(listName);
        				
            			if(cList.moveToFirst()){
            				do{
            					
            					String itemName2, quantity2, listName2;
                    			itemName2 = cList.getString(c.getColumnIndex(Constants.ITEM_NAME));
                    			quantity2 = cList.getString(c.getColumnIndex(Constants.QUANTITY_NAME));
                    			listName2 = cList.getString(c.getColumnIndex(Constants.LIST_NAME));
            					
                    			if(quantity2.equals("999")){
                    				Member newMem = new Member();
                    				newMem.setName(itemName2);
                    				newList.addMember(newMem);
                    			}
                    			else if(!itemName2.equals("first")){
                    				
                        			Log.v("test8",itemName);
                        			Log.v("test8",quantity);
                        			
                    				
                    				newList.addItem(itemName2, quantity2);
                        			}
                    			
            				}while(cList.moveToNext());
            			}
        				
            			
            			myList.add(newList);
        				subList.add(listName);
        			}
        			Log.v("test9","9");
        			}
        			
        		}while(c.moveToNext());
        	}}else{
        		isNew = true;
        	}
        		}catch(SQLiteException ex){
        			isNew = true;
        			return;
        		}
        	
    }
    
    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
    	Log.v("option","1");
    	MenuInflater inflater = getMenuInflater();
        Log.v("option","3");
        inflater.inflate(R.menu.listmenu, menu);
        Log.v("option","4");
        return true;
    }

    
    
    @Override
    public boolean onOptionsItemSelected(MenuItem item){
    	Intent intent = new Intent();
    	switch (item.getItemId()){
    	case R.id.add:
    		intent = new Intent(ShopperSidekick.this, AddList.class);
    		startActivityForResult(intent,myApp.addList);  
			break;
    	case R.id.members:
    		intent = new Intent(ShopperSidekick.this, MemberList.class);
			startActivityForResult(intent,myApp.editMember);
			break;
    	case R.id.help:
    		break;
    	}
    	return true;    	
    }
    
    @Override
    public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
    	MenuInflater inflater = getMenuInflater();
    	inflater.inflate(R.menu.contextmenu, menu);
    	if(myList.get(appInfo.getPosition()).isShopping())
        	menu.getItem(1).setTitle("End Shopping");
        else
        	menu.getItem(1).setTitle("Go Shopping");
    }
    
    @Override
    public boolean onContextItemSelected(MenuItem item) {
    	Intent intent = new Intent();
    	final ShoppingList myShoppingList = myList.get(appInfo.getPosition());
	      switch (item.getItemId()) {
	    case R.id.renamecontext:
	    	intent = new Intent(ShopperSidekick.this, RenameList.class);
    		startActivityForResult(intent,myApp.renameList); 
	        return true;
	    case R.id.editcontext:
	  		intent = new Intent(ShopperSidekick.this, ItemView.class);
	  		intent.putExtra("ShoppingListTitle",myShoppingList.getName());
	  		startActivityForResult(intent, myApp.listView);    
	        return true;
	    case R.id.goShoppingcontext:
	    	myShoppingList.setShopping();
	    	updateApp();
	    	adapter.notifyDataSetChanged();
	    	return true;
	    case R.id.deletecontext:
    		AlertDialog alertDialog = new AlertDialog.Builder(ShopperSidekick.this).create();
    		alertDialog.setTitle("Delete List");
    		alertDialog.setMessage("Delete "+myShoppingList.getName()+"?");
    		alertDialog.setButton(alertDialog.BUTTON_POSITIVE,"OK", new DialogInterface.OnClickListener() {
    		   public void onClick(DialogInterface dialog, int which) {
    			   myList.remove(myShoppingList);
    			   localDatabase.deleteList(myShoppingList.getName());
	        		   adapter.notifyDataSetChanged();
    		   }
    		});
    		
    		alertDialog.setButton(alertDialog.BUTTON_NEGATIVE,"Cancel", new DialogInterface.OnClickListener() {
        		   public void onClick(DialogInterface dialog, int which) {

        		   }
        	});
    		alertDialog.show();
    		updateApp();
	    	adapter.notifyDataSetChanged();
	    	return true;
	    case R.id.helpcontext:
	    	return true;
	    case R.id.backcontext:
	    	
	    return true;
	    }
	hint();
	return true;
    }
    private void updateApp(){
    	appInfo.setCurrentActivity(this);
        appInfo.setMemberList(myMember);
        appInfo.setShoppingList(myList);
    }
    
    // This method is used to display hints
    private void hint(){
    	TextView temp = (TextView) findViewById(R.id.hint);
    	
        if(myList.size() < 1){
        	temp.setText("Use 'add' to create a new list and use 'option' to find more options");
        	temp.setTextSize(15);
        	temp.setTextColor(Color.GRAY);
        }else{
        	temp.setText("");
        }
    }
    
    private class MyClickableShoppingListListAdapter extends MyListAdapter {  
		public MyClickableShoppingListListAdapter(List<ShoppingList> myList, Context context) {  
            super(myList,context);  
        } 
		
		
		@Override
		public View getView(final int position, View convertView, ViewGroup parent) {
	        LinearLayout ListLayout;
	        final ShoppingList myShoppingList=(ShoppingList)ContentList.get(position);
	        ListLayout= (LinearLayout) LayoutInflater.from(context).inflate(R.layout.listlistelement, parent, false);
	        TextView ListTitle=(TextView) ListLayout.findViewById(R.id.ItemTitle);
	        //Button DelButton=(Button) ListLayout.findViewById(R.id.DelButton);
	        ListTitle.setText(myShoppingList.getName());
	        
	        if(myShoppingList.isShopping())
	        	ListTitle.setTextColor(Color.GREEN);
	        else
	        	ListTitle.setTextColor(Color.GRAY);
	        
	        ListTitle.setOnLongClickListener(new OnLongClickListener(){
	        	@Override
				public boolean onLongClick(View v) {
	        		appInfo.setPosition(myList.indexOf(myShoppingList));
	        		registerForContextMenu(v);
	        		v.showContextMenu();
					return true;
				}
	        });
	        ImageView option = (ImageView) ListLayout.findViewById(R.id.list_option);
	        option.setImageResource(R.drawable.options_32);
	        option.setOnClickListener(new OnClickListener(){
				@Override
				public void onClick(View v) {
					appInfo.setPosition(myList.indexOf(myShoppingList));
	        		registerForContextMenu(v);
	        		v.showContextMenu();
				}
	        	
	        });
	        
	        ListTitle.setOnClickListener(new OnClickListener(){
	        	@Override
	        	public void onClick(View view){
	        		appInfo.setPosition(myList.indexOf(myShoppingList));
	        		Intent myIntent = new Intent(ShopperSidekick.this, ItemView.class);
	        		myIntent.putExtra("ShoppingListTitle",myShoppingList.getName());
	        		appInfo.setPosition(myList.indexOf(myShoppingList));
	        		//localDatabase.close();
	        		startActivityForResult(myIntent, myApp.listView);  
	        	}
	        });
	        return ListLayout;
		}



    }
    
   
}